package com.tamir.template.config;

import com.tamir.template.operator.parse.OperatorParser;
import com.tamir.template.operator.parse.impl.OperatorParserImpl;
import com.tamir.template.util.StringUtil;

import java.math.RoundingMode;
import java.util.HashMap;
import java.util.Map;

/**
 * @author : tanggh
 * @description : 操作符配置
 * @date : 2017/1/3
 */
public class OperatorConfig
{
    public static String symbolStr = "()+-*/=<>!&|";
    public static char[] symbolArray = symbolStr.toCharArray();
    public static char leftBracket = symbolArray[0];
    public static char rightBracket = symbolArray[1];
    public static char plus = symbolArray[2];
    public static char sub = symbolArray[3];
    public static char mul = symbolArray[4];
    public static char div = symbolArray[5];
    public static char eq = symbolArray[6];
    public static char lt = symbolArray[7];
    public static char gt = symbolArray[8];
    public static char non = symbolArray[9];
    public static char and = symbolArray[10];
    public static char or = symbolArray[11];

    public volatile int divideScale = 2;
    public volatile RoundingMode roundingMode = RoundingMode.HALF_UP;

    public static char[] eqNext = new char[]{'='};
    public static char[] gtNext = new char[]{'='};
    public static char[] ltNext = new char[]{'=', '>'};
    public static char[] nonNext = new char[]{'=', '('};
    public static char[] eqNex = new char['='];

    /**
     * 运算符解析
     */
    private OperatorParser operatorParser;

    //操作符优先级
    protected Map<String, Integer> operatorLevel = null;

    private static OperatorConfig instance;

    public static OperatorConfig getInstance(){
        if(instance == null){
            synchronized (OperatorConfig.class){
                if(instance == null){
                    instance = new OperatorConfig();
                }
            }
        }
        return instance;
    }

    private OperatorConfig(){
        init();
    }

    private void init(){
        operatorLevel = new HashMap<String, Integer>();
        //( : 9
        operatorLevel.put(String.valueOf(leftBracket), 9);
        operatorLevel.put(String.valueOf(non), 8);

        // * / : 7
        operatorLevel.put(String.valueOf(mul), 7);
        operatorLevel.put(String.valueOf(div), 7);

        operatorLevel.put(String.valueOf(plus), 6);
        operatorLevel.put(String.valueOf(sub), 6);

        operatorLevel.put("<", 4);
        operatorLevel.put(">", 4);
        operatorLevel.put(">=", 4);
        operatorLevel.put("<=", 4);

        //!=  4
        operatorLevel.put("!=", 4);
        //==  4
        operatorLevel.put("==", 4);

        operatorLevel.put("&&", 2);
        operatorLevel.put("||", 2);
        operatorParser = new OperatorParserImpl();
    }

    /**
     * 获取操作符优先级
     * @param operator
     * @return
     */
    public int getOperatorLevelByOp(String operator){
        if(StringUtil.isEmpty(operator) || !operatorLevel.containsKey(operator)){
            return -1;
        }
        return operatorLevel.get(operator).intValue
                ();
    }

    /**
     * 是否是逻辑表达式
     * @param express
     * @return
     */
    public boolean isLogicOperator(String express){
        boolean isOp = false;
        if(StringUtil.isNotEmpty(express)){
            for (char seq : symbolArray){
                if(express.indexOf(seq) != -1){
                    isOp = true;
                    break;
                }
            }
        }

        return isOp;
    }

    public int getDivideScale()
    {
        return divideScale;
    }

    public void setDivideScale(int divideScale)
    {
        this.divideScale = divideScale;
    }

    public RoundingMode getRoundingMode()
    {
        return roundingMode;
    }

    public void setRoundingMode(RoundingMode roundingMode)
    {
        this.roundingMode = roundingMode;
    }

    public OperatorParser getOperatorParser()
    {
        return operatorParser;
    }

    public void setOperatorParser(OperatorParser operatorParser)
    {
        this.operatorParser = operatorParser;
    }
}
